﻿using System.Windows;
using System.Windows.Controls;
//using Microsoft.Research.Kinect.Nui;
using Microsoft.Kinect;
using System.IO;
using Kinect;
using Imaging;

namespace KinectApplication
{
    public partial class MainWindow : UserControl
    {
        Kinect kinect;

        public MainWindow()
        {
            InitializeComponent();

            kinect = new Kinect(ParserType.Skeleton);

            //set debug image
            Debugging.image = DepthImageWithMinDistance;
            Debugging.canvas = canvas;
            Debugging.hand = Hand;
            Debugging.hand2 = Hand2;

            ReachMouseInput.AddUserControl(this);

            MouseLeftButtonDown += new System.Windows.Input.MouseButtonEventHandler(MainWindow_MouseLeftButtonDown);

          //  LoadDebugImage();
        }

        private void LoadDebugImage()
        {
            var bytes = File.ReadAllBytes(@"D:\Backup\Koulu\GRADU\Kinect\X225-Y254-Z1666.dat");

            //SkeletonParser.ShowDebug(bytes.ToDepthArray(640, 480), 225, 254, 1666);
            Debugging.ShowDepth(bytes, 640, 480);
        }

        void MainWindow_MouseLeftButtonDown(object sender, System.Windows.Input.MouseButtonEventArgs e)
        {
            //var bytes = File.ReadAllBytes(@"D:\Backup\Koulu\GRADU\Kinect\X225-Y254-Z1666.dat");

            //var depth = bytes.ToDepthArray(640, 480);

            //QueueLinearFloodFiller floodFiller = new QueueLinearFloodFiller(depth, 640, 480, 6666, true, 50);

            //floodFiller.FloodFill(new System.Drawing.Point(640 - 225, 254));

            //Debugging.ShowDepth(floodFiller.Bits, 640, 480);

            //Debugging.ShowRectangle(640 - floodFiller.Right, floodFiller.Top, (640 - floodFiller.Left) - (640 - floodFiller.Right), floodFiller.Bottom - floodFiller.Top);
           // Debugging.ShowDepth(depth, 640, 480);
           
        }

        private void UserControl_Unloaded(object sender, RoutedEventArgs e)
        {
            ReachMouseInput.RemoveUserControl(this);
            kinect.UninitializeRuntime();
        }



      //  BlobProcessor blobber = new BlobProcessor();

        //private NeuralNetwork neuralNetwork = null;

        //int _minDistance;
      //  int mouseX = 0;
       // int mouseY = 0;
        //bool _saveColorFrame;
        //bool _saveDepthFrame;
        //int threshold = 800;
        //int thresholdEnd = 1000;


        //short[] depthArray = new short[640 * 480];
        //byte[] colorFrame = new byte[640 * 480 * 4];

        //short[] backgroundNoiseMin = new short[640 * 480];
        //short[] backgroundNoiseMax = new short[640 * 480];


        // resizeBlob(e.ImageFrame.Image);

        //Floodfill(e.ImageFrame.Image);

        // Old(e.ImageFrame.Image);
        //    int backgroundCounter = 0;

        //public void MinMaxBackground(PlanarImage image)
        //{
        //    System.Diagnostics.Stopwatch timer = new System.Diagnostics.Stopwatch();
        //    timer.Start();
        //    long begin = timer.ElapsedMilliseconds;

        //    var imageWidth = image.Width;
        //    var imageHeight = image.Height;

        //    var greyIndex = 0;
        //    var colorIndex = 0;

        //    for (var y = 0; y < imageHeight; y++)
        //    {
        //        var heightOffset = y * imageWidth;

        //        for (var x = 0; x < imageWidth; x++)
        //        {
        //            short value = (short)((image.Bits[greyIndex] | image.Bits[greyIndex + 1] << 8));
        //            byte color = (byte)value;
        //            int position = (imageWidth - x - 1) + heightOffset;

        //            if (backgroundCounter < 80)
        //            {
        //                if (value > backgroundNoiseMax[position])
        //                {
        //                    backgroundNoiseMax[position] = value;
        //                }

        //                if (value < backgroundNoiseMin[position] && value > 0)
        //                {
        //                    backgroundNoiseMin[position] = value;
        //                }
        //            }

        //            else
        //            {
        //                if (value < backgroundNoiseMax[position] + 10 && value > backgroundNoiseMin[position] - 10)
        //                {
        //                    colorFrame[colorIndex + ImageProcessing.BlueIndex] = 0;
        //                }
        //                else
        //                {
        //                    depthArray[position] = value;

        //                    //4ms
        //                  //  colorFrame[colorIndex + ImageProcessing.RedIndex] = color;
        //                  //  colorFrame[colorIndex + ImageProcessing.GreenIndex] = color;
        //                    colorFrame[colorIndex + ImageProcessing.BlueIndex] = color;
        //                }

        //                colorIndex = position * 4;
        //            }

        //            greyIndex += 2;
        //        }

        //    }

        //    if (backgroundCounter < 80)
        //    {
        //        backgroundCounter++;
        //    }

        //    BitmapSource s = BitmapSource.Create(640, 480, 96, 96, PixelFormats.Bgr32, null, colorFrame, 640 * PixelFormats.Bgr32.BitsPerPixel / 8);

        //    DepthImageWithMinDistance.Source = s;

        //    long end = timer.ElapsedMilliseconds;
        //    info.Text = String.Format("frame: {0} ms", end - begin);

        //}

        //public void Floodfill(PlanarImage image)
        //{
        //    System.Diagnostics.Stopwatch timer = new System.Diagnostics.Stopwatch();
        //    timer.Start();
        //    long begin = timer.ElapsedMilliseconds;

        //    var imageWidth = image.Width;
        //    var imageHeight = image.Height;

        //    var greyIndex = 0;
        //    var colorIndex = 0;

        //    for (var y = 0; y < imageHeight; y++)
        //    {
        //        var heightOffset = y * imageWidth;

        //        for (var x = 0; x < imageWidth; x++)
        //        {
        //            short value = (short)((image.Bits[greyIndex] | image.Bits[greyIndex + 1] << 8));
        //            byte color = (byte)value;
        //            int position = (imageWidth - x - 1) + heightOffset;

        //            if (value < 1000)
        //            {
        //                depthArray[position] = value;
        //            }
        //            else
        //            {
        //                depthArray[position] = 0;
        //            }

        //            //4ms
        //            colorFrame[colorIndex + ImageProcessing.RedIndex] = color;
        //            colorFrame[colorIndex + ImageProcessing.GreenIndex] = color;
        //            colorFrame[colorIndex + ImageProcessing.BlueIndex] = color;

        //            colorIndex = position * 4;

        //            greyIndex += 2;
        //        }


        //    }



        //    BitmapSource s = BitmapSource.Create(640, 480, 96, 96, PixelFormats.Bgr32, null, colorFrame, 640 * PixelFormats.Bgr32.BitsPerPixel / 8);

        //    DepthImageWithMinDistance.Source = s;

        //    positions = blobber.Process(depthArray);

        //    canvas.Children.Clear();

        //    foreach (var item in positions)
        //    {
        //        Ellipse elli = new Ellipse() { Width = 50, Height = 50, Stroke = new SolidColorBrush(Colors.Red) };
        //        Canvas.SetLeft(elli, item.Key.X - 25);
        //        Canvas.SetTop(elli, item.Key.Y - 25);

        //        canvas.Children.Add(elli);
        //    }

        //    long end = timer.ElapsedMilliseconds;
        //    info.Text = String.Format("frame: {0} ms", end - begin);

        //}

        //public void resizeBlob(PlanarImage image)
        //{    
        //    System.Diagnostics.Stopwatch timer = new System.Diagnostics.Stopwatch();
        //    timer.Start();
        //    long begin = timer.ElapsedMilliseconds;

        //    var imageWidth = image.Width;
        //    var imageHeight = image.Height;

        //    threshold = 4000;
        //    var greyIndex = 0;
        //    int colorIndex = 0;

        //    for (var y = 0; y < imageHeight; y++)
        //    {
        //        var heightOffset = y * imageWidth;

        //        for (var x = 0; x < imageWidth; x++)
        //        {
        //            short value = (short)((image.Bits[greyIndex] | image.Bits[greyIndex + 1] << 8));
        //            int position = (imageWidth - x - 1) + heightOffset;

        //            //threshold cutoff
        //            if (value > 0 && value < threshold)
        //            {
        //                threshold = value;
        //            }

        //            if (background != null)
        //            {
        //                if (value > 0)
        //                {
        //                    int error = (value / 15) - 25;

        //                    //more further away, more useless jitter, also filter out 3m+ values
        //                    if (Math.Abs(background[position] - value) < error || value > 3000)
        //                    {
        //                        value = 0;
        //                    }
        //                }
        //            }

        //            depthArray[position] = value;

        //            greyIndex += 2;

        //            colorIndex = position * 4;
        //        }

        //    }

        //    if (background == null)
        //    {
        //        background = new short[640 * 480];

        //        depthArray.CopyTo(background, 0);
        //    }

        //    thresholdEnd = threshold + 400;

        //    for (int i = 0, depthIndex = 0; i < colorFrame.Length; i += 4, depthIndex++)
        //    {

        //        if (depthArray[depthIndex] <= thresholdEnd && depthArray[depthIndex] > threshold)
        //        {
        //            byte r = (byte)(depthArray[depthIndex] - threshold);
        //            byte b = (byte)(depthArray[depthIndex] - threshold / 2);
        //            byte g = (byte)(depthArray[depthIndex] - threshold / 4);

        //            colorFrame[i + ImageProcessing.RedIndex] = r;
        //            colorFrame[i + ImageProcessing.GreenIndex] = g;
        //            colorFrame[i + ImageProcessing.BlueIndex] = b;
        //        }
        //        else
        //        {
        //            colorFrame[i + ImageProcessing.RedIndex] = 0;
        //            colorFrame[i + ImageProcessing.GreenIndex] = 0;
        //            colorFrame[i + ImageProcessing.BlueIndex] = 0;
        //        }

        //    }

        //    var source = colorFrame.ToBitmapSource(imageWidth, imageHeight);

        //    DepthImageWithMinDistance.Source = source;

        //    positions.Clear();


        //    //var bibi = CopyDataToBitmap(image.Bits);

        //    //var bubu = ResizeBitmap2(bibi, 32, 24);

        //  //  var bibi2 = new Bitmap(bibi, 32, 24);

        //    //var bitmap = depthArray.ToBitmapSource(640, 480);
        //   // var small = FastResize(bitmap, 32, 24);
        //   // byte[] pix = new byte[32 * 24 * 4];


        //  //  small.CopyPixels(pix, 32 * 2, 0);

        //    //RawDepthSmall.Source = bubu;

        //    //for (int i = 0; i < 32; i++)
        //    //{
        //    //    for (int j = 0; j < 24; j++)
        //    //    {
        //    //        var jee = bubu.GetPixel(i, j);

        //    //        int position = j * 24 + i;

        //    //        pix[position + ImageProcessing.RedIndex] = jee.B;
        //    //        pix[position + ImageProcessing.GreenIndex] = jee.R;
        //    //        pix[position + ImageProcessing.BlueIndex] = jee.G;
        //    //    }
        //    //}

        //    //RawDepthSmall.Source = pix.ToBitmapSource(32, 24);

        //   // BlobResize(depthArray.ToBitmapSource(640, 480).ToBitmap());

        //    canvas.Children.Clear();

        //    foreach (var item in positions)
        //    {
        //        Ellipse elli = new Ellipse() { Width = Math.Sqrt(item.Value) * 10, Height = Math.Sqrt(item.Value) * 10, Stroke = new SolidColorBrush(Colors.Red) };
        //        Canvas.SetLeft(elli, item.Key.X * 20);
        //        Canvas.SetTop(elli, item.Key.Y * 20);

        //        canvas.Children.Add(elli);
        //    }

        //    long end = timer.ElapsedMilliseconds;
        //    System.Diagnostics.Trace.WriteLine(String.Format("asd: {0} ms", end - begin));

        //    info.Text = String.Format("frame: {0} ms", end - begin);
        //}

        //byte blobTreshold = 230;

        //private double[] BitmapToMatrix(BitmapSource Temp)
        //{
        //    Temp = FastResize(Temp, av_ImageWidth, av_ImageHeight);

        //    WriteableBitmap bibi = new WriteableBitmap(Temp);

        //    int stride = Temp.PixelWidth * ((Temp.Format.BitsPerPixel + 7) / 8);

        //    var pixelBytes = new byte[Temp.PixelHeight * stride];
        //    bibi.CopyPixels(pixelBytes, stride, 0);

        //    PixelColor[,] colors = new PixelColor[Temp.PixelWidth, Temp.PixelHeight];

        //    for (int y = 0; y < Temp.PixelHeight; y++)
        //    {
        //        for (int x = 0; x < Temp.PixelWidth; x++)
        //        {
        //            colors[x, y] = new PixelColor
        //            {
        //                Blue = (byte)(255 - pixelBytes[(y * Temp.PixelWidth + x) * 4 + 0]),
        //                Green = (byte)(255 - pixelBytes[(y * Temp.PixelWidth + x) * 4 + 1]),
        //                Red = (byte)(255 - pixelBytes[(y * Temp.PixelWidth + x) * 4 + 2]),
        //                Alpha = pixelBytes[(y * Temp.PixelWidth + x) * 4 + 3],
        //            };


        //        }
        //    }

        //    //CopyPixels(Temp, colors, av_ImageWidth * 4, 0);

        //    double HRate = ((Double)av_ImageHeight / Temp.Height);
        //    double WRate = ((Double)av_ImageWidth / Temp.Width);
        //    double[] Result = new double[av_ImageWidth * av_ImageHeight];


        //    for (int r = 0; r < av_ImageHeight; r++)
        //    {
        //        for (int c = 0; c < av_ImageWidth; c++)
        //        {
        //            var color = colors[(int)(c / WRate), (int)(r / HRate)];
        //            Result[r * av_ImageWidth + c] = 1 - (color.Red * .3 + color.Green * .59 + color.Blue * .11) / 255;
        //            //Result[r * av_ImageWidth + c] = (double)colors[(int)(c / WRate), (int)(r / HRate)].Blue / 255;
        //        }
        //    }

        //    return Result;
        //}



        //[StructLayout(LayoutKind.Sequential)]
        //public struct PixelColor
        //{
        //    public byte Blue;
        //    public byte Green;
        //    public byte Red;
        //    public byte Alpha;
        //}


        //short[] background;



        //public void Old(PlanarImage image)
        //{
        //    System.Diagnostics.Stopwatch timer = new System.Diagnostics.Stopwatch();
        //    timer.Start();
        //    long begin = timer.ElapsedMilliseconds;

        //    var imageWidth = image.Width;
        //    var imageHeight = image.Height;


        //    byte[] raw = new byte[640 * 480 * 4];
        //    threshold = 4000;
        //    var greyIndex = 0;
        //    int colorIndex = 0;

        //    int xLocation = 0;
        //    int yLocation = 0;
        //    int counter = 0;

        //    for (var y = 0; y < imageHeight; y++)
        //    {
        //        var heightOffset = y * imageWidth;

        //        for (var x = 0; x < imageWidth; x++)
        //        {
        //            short value = (short)((image.Bits[greyIndex] | image.Bits[greyIndex + 1] << 8));
        //            int position = (imageWidth - x - 1) + heightOffset;

        //            //threshold cutoff
        //            if (value > 0 && value < threshold)
        //            {
        //                threshold = value;
        //            }

        //            if (background != null)
        //            {
        //                if (value > 0)
        //                {
        //                    int error = (value / 15) - 25;

        //                    //more further away, more useless jitter, also filter out 3m+ values
        //                    if (Math.Abs(background[position] - value) < error || value > 3000)
        //                    {
        //                        value = 0;
        //                    }
        //                }
        //            }

        //            depthArray[position] = value;

        //            greyIndex += 2;

        //            raw[colorIndex + ImageProcessing.RedIndex] = (byte)(value);
        //            raw[colorIndex + ImageProcessing.GreenIndex] = (byte)(value / 2);
        //            raw[colorIndex + ImageProcessing.BlueIndex] = (byte)(value / 3);

        //            colorIndex = position * 4;
        //        }

        //    }

        //    //  var rawSource =  raw.ToBitmapSource(imageWidth, imageHeight);

        //    // RawDepth.Source = rawSource;



        //    if (background == null)
        //    {
        //        background = new short[640 * 480];

        //        depthArray.CopyTo(background, 0);
        //    }

        //    thresholdEnd = threshold + 250;




        //    int pX = 0;
        //    int pY = 0;

        //    for (int i = 0, depthIndex = 0; i < colorFrame.Length; i += 4, depthIndex++)
        //    {
        //        pX++;

        //        if (pX >= 640)
        //        {
        //            pY++;
        //            pX = 0;
        //        }

        //        if (depthArray[depthIndex] <= thresholdEnd && depthArray[depthIndex] > threshold)
        //        {
        //            byte r = (byte)(depthArray[depthIndex] - threshold);
        //            byte b = (byte)(depthArray[depthIndex] - threshold / 2);
        //            byte g = (byte)(depthArray[depthIndex] - threshold / 4);

        //            colorFrame[i + ImageProcessing.RedIndex] = r;
        //            colorFrame[i + ImageProcessing.GreenIndex] = g;
        //            colorFrame[i + ImageProcessing.BlueIndex] = b;

        //            if (r > 200)
        //            {
        //                xLocation += pX;
        //                yLocation += pY;

        //                counter++;
        //            }

        //        }
        //        else
        //        {
        //            colorFrame[i + ImageProcessing.RedIndex] = 0;
        //            colorFrame[i + ImageProcessing.GreenIndex] = 0;
        //            colorFrame[i + ImageProcessing.BlueIndex] = 0;
        //        }


        //    }

        //    var source = colorFrame.ToBitmapSource(imageWidth, imageHeight);
        //    // var smallSource = colorFrame.ToBitmapSource(32, 24);

        //    DepthImageWithMinDistance.Source = source;

        //    MahBlob(source.ToBitmap());

        //    canvas.Children.Clear();

        //    foreach (var item in positions)
        //    {
        //        Ellipse elli = new Ellipse() { Width = Math.Sqrt(item.Value) * 10, Height = Math.Sqrt(item.Value) * 10, Stroke = new SolidColorBrush(Colors.Red) };
        //        Canvas.SetLeft(elli, item.Key.X * 20);
        //        Canvas.SetTop(elli, item.Key.Y * 20);

        //        canvas.Children.Add(elli);
        //    }

        //    //RawDepthSmall.Source = FastResize(source, 32, 24);

        //    //if (counter > 0)
        //    //{
        //    //    xLocation /= counter;
        //    //    yLocation /= counter;
        //    //}

        //    //// Point p = depthArray.GetMidpoint(imageWidth, imageHeight, 0, 0, 640, 480, threshold, thresholdEnd);





        //    //if (counter > 0)
        //    //{
        //    //    var depth = depthArray[xLocation + 640 * yLocation];


        //    //    Hand.Source = crop;

        //    //    var arr = BitmapToMatrix(crop);
        //    //    // double[] input = ImageProcessing.ToMatrix(drawingPanel1.ImageOnPanel, av_ImageHeight, av_ImageWidth);

        //    //    string MatchedHigh = "?", MatchedLow = "?";
        //    //    double OutputValueHight = 0, OutputValueLow = 0;

        //    //    if (neuralNetwork != null && neuralNetwork.done)
        //    //    {
        //    //        neuralNetwork.Recognize(arr, ref MatchedHigh, ref OutputValueHight, ref MatchedLow, ref OutputValueLow);
        //    //    }

        //    //    Title = MatchedHigh + " - " + OutputValueHight;

        //    //    if (MatchedHigh == "Hs" && OutputValueHight > 0.8)
        //    //    {

        //    //        NativeMethods.SendMouseInput(xLocation * 5 - 250, (int)(yLocation * 4) - 250, (int)System.Windows.SystemParameters.PrimaryScreenWidth, (int)System.Windows.SystemParameters.PrimaryScreenHeight, false);
        //    //    }
        //    //    else if (OutputValueHight > 0.8)
        //    //    {
        //    //        // NativeMethods.SendMouseInput(xLocation * 5 - 250, (int)(yLocation * 4) - 250, (int)System.Windows.SystemParameters.PrimaryScreenWidth, (int)System.Windows.SystemParameters.PrimaryScreenHeight, true);
        //    //    }
        //    //}

        //    //depthArray.ToBitmapSource(imageWidth, imageHeight, _minDistance, Color.FromArgb(255, 255, 0, 0));

        //    long end = timer.ElapsedMilliseconds;
        //    System.Diagnostics.Trace.WriteLine(String.Format("asd: {0} ms", end - begin));
        //    //Title = String.Format("asd: {0} ms", end - begin);
        //}

        //BitmapSource source;
        //byte[] pixelBytes;
        //System.Windows.Point p = new System.Windows.Point();
        //int count = 0;
        //Dictionary<System.Windows.Point, int> positions = new Dictionary<System.Windows.Point, int>();
        //int width;
        //int height;
        //UnsafeBitmap uns;

        //private void MahBlob(Bitmap bitmap)
        //{
        //    Bitmap buu = new Bitmap(bitmap, 32, 24);

        //    //tällä resizellä on about sama nopeus
        //    //uns = new UnsafeBitmap(ResizeBitmap(bitmap, 32, 24));
        //    uns = new UnsafeBitmap(buu);

        //    width = 32;
        //    height = 24;

        //    uns.LockBitmap();

        //    positions.Clear();

        //    for (int x = 0; x < 32; x++)
        //    {
        //        for (int y = 0; y < 24; y++)
        //        {
        //            if (uns.GetPixel(x, y).blue > 100)
        //            {
        //                p = new System.Windows.Point();
        //                count = 0;

        //                //Fill2(x, y);

        //                p.X /= count;
        //                p.Y /= count;

        //                positions.Add(p, count);
        //            }
        //        }
        //    }

        //    uns.UnlockBitmap();
        //    uns.Dispose();
        //}
    }

}
